package com.liujun.io.nio.mysql.protocol;

import java.io.UnsupportedEncodingException;
import java.nio.ByteBuffer;

import com.liujun.io.nio.mysql.bean.protocol.result.ColumnPackageBean;
import com.liujun.io.nio.mysql.bean.protocol.result.EofPackageBean;
import com.liujun.io.nio.mysql.bean.protocol.result.ResultSetHanderBean;
import com.liujun.io.nio.mysql.bean.protocol.result.RowDataPackageBean;
import com.liujun.io.nio.mysql.protocol.inf.DataParseInf;

public class ResultSetRead {

    public void readResultset(ByteBuffer allData) {

        // 获取列数量
        ByteBuffer columnNum = this.readLength(allData);

        // ,1[Result Set Header] 列数量
        DataParseInf<ResultSetHanderBean> resultDataColumnNum = new ResultSetHanderBean();

        ResultSetHanderBean columnNumPackage = resultDataColumnNum.readPackage(columnNum);

        // 2,循环列信息
        DataParseInf<ColumnPackageBean> columnDataProcess = new ColumnPackageBean();
        for (int i = 0; i < columnNumPackage.getFieldCount(); i++) {
            // 获取列数量
            ByteBuffer colmnuItem = this.readLength(allData);

            // 进行循环列信息
            ColumnPackageBean column = columnDataProcess.readPackage(colmnuItem);
        }

        // 获取列数量
        ByteBuffer eofPackage = this.readLength(allData);

        // 3,列结束
        DataParseInf<EofPackageBean> eofPackageProcess = new EofPackageBean();
        eofPackageProcess.readPackage(eofPackage);

        // 4，进行行数据读取
        DataParseInf<RowDataPackageBean> rowDataProcess = null;

        ByteBuffer rowDataBuffer = this.readLength(allData);
        // 读取报文
        while (!checkEofAackage(rowDataBuffer)) {
            rowDataProcess = new RowDataPackageBean(columnNumPackage.getFieldCount());
            RowDataPackageBean rowData = rowDataProcess.readPackage(rowDataBuffer);
            try {
                System.out.println("读取的行数据：" + new String(rowData.getFieldValue().get(1), "UTF-8"));
            } catch (UnsupportedEncodingException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            }
            rowDataBuffer = this.readLength(allData);
        }

        // 读取最后的eof报文
        eofPackageProcess.readPackage(rowDataBuffer);
        // 5,一直读取到EOF报文为止

    }

    /**
     * 检查是否为eof的标识
    * 方法描述
    * @param copyBuf
    * @return
    * @创建日期 2016年12月14日
    */
    public boolean checkEofAackage(ByteBuffer copyBuf) {
        // 以当前的position坐标标，向后读取4个
        int currPositon = copyBuf.position();
        // 读取新坐标
        if (copyBuf.limit() >= currPositon + 4) {
            copyBuf.position(currPositon + 4);
            byte bufValue = copyBuf.get();
            if (bufValue == EofPackageBean.DEFVALUE) {
                // 重新设置为老坐标
                copyBuf.position(currPositon);
                return true;
            }

            copyBuf.position(currPositon);
        }

        return false;
    }

    private ByteBuffer readLength(ByteBuffer mapBuf) {

        int currPosition = mapBuf.position();
        // HandshakeBean handshake = new HandshakeBean();
        int offset = currPosition;
        // 1获取长度信息, 占3位
        int length = getLength(mapBuf, offset);

        mapBuf.position(currPosition);
        ByteBuffer copyBuf = mapBuf.slice();
        copyBuf.limit(length);
        mapBuf.position(currPosition + length);

        return copyBuf;
    }

    public int getLength(ByteBuffer buffer, int offset) {
        // mysql包头的长度
        int msyql_packetHeaderSize = 4;
        int length = buffer.get(offset) & 0xff;
        length |= (buffer.get(++offset) & 0xff) << 8;
        length |= (buffer.get(++offset) & 0xff) << 16;
        return length + msyql_packetHeaderSize;
    }

}
